// ZOOP by Andrew Davies
//
// A copy of an old SNES game of the same name.
// The screen is made up of five boards. Each board is 4x4 units (squares). The player 
// can move around the center board. The jiras (baddy/enemy) incroach on each of 
// the boards arranged at each side of the player board. The player can 'resolve' 
// a jira by firing itself at it. It resolves all the jiras of the same colour 
// until there's no more along that direction or it hits one of a different colour 
// at which point the player and jira swap colours. The game ends if a jir encrouches 
// onto the player's board.

// Remeber to use http://www.jslint.com/ from time to time.

// Some random colours to use.
//98A89E
//BAC0AC
//FAFAC6
//FF4411
//D40015

"use strict";

// Some useful global variables.
var canvas = document.getElementById('zoop');
var context = canvas.getContext('2d');
var inputsrc = document/*.getElementById('zoop')*/;

// Try to deal with each platform's possible requestAnimationFrame. This lets me just 
// call requestAnimFrame on all (hopefully).
window.requestAnimFrame = (function(callback)
{
	return	window.requestAnimationFrame || 
			window.webkitRequestAnimationFrame || 
			window.mozRequestAnimationFrame || 
			window.oRequestAnimationFrame || 
			window.msRequestAnimationFrame ||
			function(callback) 
			{
				window.setTimeout(callback, 1000 / 60);
			};
})();

var g_ZoopColours = new Array();
g_ZoopColours.push( "blue" );
g_ZoopColours.push( "red" );
g_ZoopColours.push( "yellow" );
g_ZoopColours.push( "green" );

var g_ZoopHexColours = new Array();
g_ZoopHexColours[ g_ZoopColours[ 0 ] ] = "rgba(0, 0, 255, 0.5)"; // "#5CACEE";
g_ZoopHexColours[ g_ZoopColours[ 1 ] ] = "rgba(255, 0, 0, 0.5)"; // "#BE2625";
g_ZoopHexColours[ g_ZoopColours[ 2 ] ] = "rgba(255, 255, 0, 0.5)"; // "#FFE303";
g_ZoopHexColours[ g_ZoopColours[ 3 ] ] = "rgba(0, 255, 0, 0.5)"; // "#A2BC13";

var TOTAL_BOARD_SIZE = 360;

var g_boardTopLeft = new Vec2( 0, 0 );
var g_boardBottomRight = new Vec2( TOTAL_BOARD_SIZE, TOTAL_BOARD_SIZE );

var SUB_BOARD_NUM_UNITS_X = 4;
var SUB_BOARD_NUM_UNITS_Y = 4;
var TOTAL_BOARD_NUM_UNITS_X = SUB_BOARD_NUM_UNITS_X * 3;
var TOTAL_BOARD_NUM_UNITS_Y = SUB_BOARD_NUM_UNITS_Y * 3;

var BOARD_UNIT_SIZE_X = TOTAL_BOARD_SIZE / TOTAL_BOARD_NUM_UNITS_X;
var BOARD_UNIT_SIZE_Y = BOARD_UNIT_SIZE_X;
var g_boardUnitSize = new Vec2( BOARD_UNIT_SIZE_X, BOARD_UNIT_SIZE_Y );
var g_halfBoardUnitSize = new Vec2( BOARD_UNIT_SIZE_X / 2, BOARD_UNIT_SIZE_Y / 2 );

//....bbbb....
//....bbbb....
//....bbbb....
//....bbbb....
//bbbbppppbbbb
//bbbbppppbbbb
//bbbbppppbbbb
//bbbbppppbbbb
//....bbbb....
//....bbbb....
//....bbbb....
//....bbbb....

var CENTER_SUB_BOARD_TOP_LEFT_X = BOARD_UNIT_SIZE_X * SUB_BOARD_NUM_UNITS_X;
var CENTER_SUB_BOARD_TOP_LEFT_Y = BOARD_UNIT_SIZE_Y * SUB_BOARD_NUM_UNITS_Y;

var TOP_SUB_BOARD_TOP_LEFT_X = BOARD_UNIT_SIZE_X * ( SUB_BOARD_NUM_UNITS_X * 1 );
var TOP_SUB_BOARD_TOP_LEFT_Y = BOARD_UNIT_SIZE_Y * ( SUB_BOARD_NUM_UNITS_Y * 0 );

var BOTTOM_SUB_BOARD_TOP_LEFT_X = BOARD_UNIT_SIZE_X * ( SUB_BOARD_NUM_UNITS_X * 1 );
var BOTTOM_SUB_BOARD_TOP_LEFT_Y = BOARD_UNIT_SIZE_Y * ( SUB_BOARD_NUM_UNITS_Y * 2 );

var LEFT_SUB_BOARD_TOP_LEFT_X = BOARD_UNIT_SIZE_X * ( SUB_BOARD_NUM_UNITS_X * 0 );
var LEFT_SUB_BOARD_TOP_LEFT_Y = BOARD_UNIT_SIZE_Y * ( SUB_BOARD_NUM_UNITS_Y * 1 );

var RIGHT_SUB_BOARD_TOP_LEFT_X = BOARD_UNIT_SIZE_X * ( SUB_BOARD_NUM_UNITS_X * 2 );
var RIGHT_SUB_BOARD_TOP_LEFT_Y = BOARD_UNIT_SIZE_Y * ( SUB_BOARD_NUM_UNITS_Y * 1 );

var CENTER_SUB_BOARD_COLOUR_A = "#0034CC";
var CENTER_SUB_BOARD_COLOUR_B = "#FF3300";

var BADDY_SUB_BOARD_COLOUR_A = "#98A89E";
var BADDY_SUB_BOARD_COLOUR_B = "#FAFAC6";

var inputArray = new Array();
inputsrc.addEventListener('keydown', function(e) 
{
	inputArray.push( e.keyCode )
	//inputArray.push( e.charCode )	
}, false);
inputsrc.addEventListener('keypress', function(e) 
{
	inputArray.push( e.charCode )	
}, false);

var g_frameIdx = 0;
var g_player = new ZoopPlayer( ( SUB_BOARD_NUM_UNITS_X * 1 ), ( SUB_BOARD_NUM_UNITS_Y * 1 ), g_frameIdx );
var g_boards = new Array();

g_boards[ "center" ] = new ZoopBoard( 
	CENTER_SUB_BOARD_TOP_LEFT_X, CENTER_SUB_BOARD_TOP_LEFT_Y,
	( SUB_BOARD_NUM_UNITS_X * 1 ), ( SUB_BOARD_NUM_UNITS_Y * 1 ),
	0, 0, 0, 0, 0, 0,
	CENTER_SUB_BOARD_COLOUR_A, CENTER_SUB_BOARD_COLOUR_B,
	"none" );
	
g_boards[ "top" ] = new ZoopBoard( 
	TOP_SUB_BOARD_TOP_LEFT_X, TOP_SUB_BOARD_TOP_LEFT_Y, 
	( SUB_BOARD_NUM_UNITS_X * 1 ), ( SUB_BOARD_NUM_UNITS_Y * 0 ),
	0, 1, 0, 0, 1, 0,
	BADDY_SUB_BOARD_COLOUR_A,BADDY_SUB_BOARD_COLOUR_B,
	"down" );
	
g_boards[ "bottom" ] = new ZoopBoard( 
	BOTTOM_SUB_BOARD_TOP_LEFT_X, BOTTOM_SUB_BOARD_TOP_LEFT_Y, 
	( SUB_BOARD_NUM_UNITS_X * 1 ), ( SUB_BOARD_NUM_UNITS_Y * 2 ),
	0 , -1, ( SUB_BOARD_NUM_UNITS_X - 1 ), ( SUB_BOARD_NUM_UNITS_Y - 1 ), -1, 0,
	BADDY_SUB_BOARD_COLOUR_A,BADDY_SUB_BOARD_COLOUR_B,
	"up" );
	
g_boards[ "left" ] = new ZoopBoard( 
	LEFT_SUB_BOARD_TOP_LEFT_X, LEFT_SUB_BOARD_TOP_LEFT_Y, 
	( SUB_BOARD_NUM_UNITS_X * 0 ), ( SUB_BOARD_NUM_UNITS_Y * 1 ),
	1, 0, 0, ( SUB_BOARD_NUM_UNITS_Y - 1 ), 0, -1,	
	BADDY_SUB_BOARD_COLOUR_A,BADDY_SUB_BOARD_COLOUR_B,
	"right" );
	
g_boards[ "right" ] = new ZoopBoard( 
	RIGHT_SUB_BOARD_TOP_LEFT_X, RIGHT_SUB_BOARD_TOP_LEFT_Y,
	( SUB_BOARD_NUM_UNITS_X * 2 ), ( SUB_BOARD_NUM_UNITS_Y * 1 ),
	-1, 0, ( SUB_BOARD_NUM_UNITS_X - 1 ), 0, 0, 1,	
	BADDY_SUB_BOARD_COLOUR_A,BADDY_SUB_BOARD_COLOUR_B,
	"left" );

var g_newBaddyFrame = 0;

//var g_DebugGraphicsLine = new DebugGraphicsLine( 
//	CENTER_SUB_BOARD_TOP_LEFT_X - 20,
//	CENTER_SUB_BOARD_TOP_LEFT_Y - 21,
//	RIGHT_SUB_BOARD_TOP_LEFT_X + 30,
//	BOTTOM_SUB_BOARD_TOP_LEFT_Y + 90,
//	40, // width
//	255, 255, 0, 0.5 ); // red, green, blue, alpha )



// Draw ---------------------------------------------------------
// Draw ---------------------------------------------------------
// Draw ---------------------------------------------------------

function draw()
{
	// Start with a clean sheet
	context.clearRect(0, 0, canvas.width, canvas.height);
	
	for( var boardIdx in g_boards )
	{
		g_boards[ boardIdx ].draw( g_frameIdx );		
	}

	g_player.draw( g_frameIdx );	
	
	debugGraphicsDraw();
}

// Draw ---------------------------------------------------------
// Draw ---------------------------------------------------------
// Draw ---------------------------------------------------------


// Update -------------------------------------------------------
// Update -------------------------------------------------------
// Update -------------------------------------------------------

function update() 
{
	// Process input
	while( inputArray.length != 0 )
	{
		var input = inputArray[ inputArray.length - 1 ];
		
		g_player.input( input ); //, g_frameIdx );
		
		inputArray.pop();
	}
	
	// Update
	{	
		// Is it time for a new row of baddies
		if( g_frameIdx >= g_newBaddyFrame )
		{
			g_boards[ "top" ].addBaddies( g_frameIdx );	
			g_boards[ "bottom" ].addBaddies( g_frameIdx );	
			g_boards[ "left" ].addBaddies( g_frameIdx );	
			g_boards[ "right" ].addBaddies( g_frameIdx );	
		
			// Next baddies to arrive in this many frames time.
			g_newBaddyFrame = g_frameIdx + ( 60 * 20 );
		}

		for( var boardIdx in g_boards )
		{
			g_boards[ boardIdx ].update( g_frameIdx );		
		}		
		
		g_player.update( g_frameIdx, g_boards );
	}
	

	// Draw
	draw();

	// keep going
    window.requestAnimFrame(update);
	g_frameIdx++;
}

// Update -------------------------------------------------------
// Update -------------------------------------------------------
// Update -------------------------------------------------------

// Init ---------------------------------------------------------
// Init ---------------------------------------------------------
// Init ---------------------------------------------------------

(function init() {
    window.requestAnimFrame(update);
})();

// Init ---------------------------------------------------------
// Init ---------------------------------------------------------
// Init ---------------------------------------------------------




